#include "InputManager.h"

InputManager::InputManager()
{
	startDetectionDoubleClick = false;
	for(int i=0;i<4;i++)
	{
		mouseDownTimeCount[i] = 0;
	}
}
void InputManager::initDInput(HINSTANCE hInstance, HWND hWnd)
{
	DirectInput8Create(hInstance,DIRECTINPUT_VERSION,IID_IDirectInput8,(void **)&din,NULL);
	din->CreateDevice(GUID_SysKeyboard,&dinKeyboard,NULL);
	din->CreateDevice(GUID_SysMouse,&dinMouse,NULL);
	dinKeyboard->SetDataFormat(&c_dfDIKeyboard);
	dinMouse->SetDataFormat(&c_dfDIMouse);
	dinKeyboard->SetCooperativeLevel(hWnd,DISCL_NONEXCLUSIVE|DISCL_FOREGROUND|DISCL_NOWINKEY);
	dinMouse->SetCooperativeLevel(hWnd,DISCL_EXCLUSIVE|DISCL_FOREGROUND);
}

void InputManager::detectInput(void)
{
	dinKeyboard->Acquire();
	dinMouse->Acquire();
	dinKeyboard->GetDeviceState(256,(LPVOID)keyState);
	dinMouse->GetDeviceState(sizeof(DIMOUSESTATE),(LPVOID)&mouseState);

	/*if(keyState[DIK_LEFT]&0x80)
	DIK_EscAPE;
	DIK_0-9;
	DIK_MINUS;
	DIK_EQUALS;
	DIK_LCONTROL;
	DIK_UP;
	DIK_DOWN;
	DIK_LEFT;
	DIK_RIGHT;*/
}
void InputManager::setMousePosition()
{
	mousePos.x += mouseState.lX/1.0f;
	mousePos.y += mouseState.lY/1.0f;
}
void InputManager::changeMouseTimeUpOrDown(byte button)
{
	if(isButtonPressed(button))
	{
		mouseDownTimeCount[button]+=1;
	}
	else
	{
		mouseDownTimeCount[button]=0;
	}
	if(wasButtonPressed(button))
	{
		mouseDownTime[button]=GetTickCount();
	}
	if(wasButtonReleased(button))
	{
		mouseUpTime[button]=GetTickCount();
	}
	if(wasButtonPressed(0))
	{
		oldMousePos = mousePos;
	}
}
bool InputManager::isKeyPressed(byte key)
{
	if(keyState[key]&0x80)
	{
		return true;
	}
	return false;
}
bool InputManager::isButtonPressed(byte button)
{
	if(mouseState.rgbButtons[button]&0x80)
	{
		return true;
	}
	return false;
}
bool InputManager::wasButtonPressed(byte button)
{
	if((mouseState.rgbButtons[button]&0x80)&&!(oldMouseState.rgbButtons[button]&0x80))
	{
		return true;
	}
	return false;
}
bool InputManager::wasButtonReleased(byte button)
{
	if(!(mouseState.rgbButtons[button]&0x80)&&(oldMouseState.rgbButtons[button]&0x80))
	{
		return true;
	}
	return false;
}
bool InputManager::wasKeyPressed(byte key)
{
	if((keyState[key]&0x80)&&!(oldKeyState[key]&0x80))
	{
		return true;
	}
	return false;
}
bool InputManager::wasKeyReleased(byte key)
{
	if(!(keyState[key]&0x80)&&(oldKeyState[key]&0x80))
	{
		return true;
	}
	return false;
}
bool InputManager::isKeyReleased(byte key)
{
	if(!isKeyPressed(key))
	{
		return true;
	}
	return false;
}
void InputManager::cleanDInput(void)
{
	dinKeyboard->Unacquire();
	dinMouse->Unacquire();
	din->Release();
}
bool InputManager::getGesture(int type)
{
	if(isButtonPressed(0)||wasButtonPressed(0))
		startDetectionDoubleClick = true;
	bool returnValue = false;
	switch(type)
	{
		case LongClick:
			if(mouseDownTimeCount[0]>TIME_TO_LONG_CLICK)
				returnValue = true;
			break;
		case DoubleClick:
			if((wasButtonPressed(0))&&((mouseDownTime[0]-mouseUpTime[0])<TIME_TO_DOUBLE_CLICK)&&(startDetectionDoubleClick))
				returnValue = true;
			break;
		case Drag:
			if((isButtonPressed(0))&&(distanceVector(mousePos,oldMousePos)>(DISTANCE_TO_DRAG*DISTANCE_TO_DRAG)))
				returnValue = true;
			break;
		default:
			returnValue = false;
	}
	return returnValue;
}
void InputManager::Update(int dt)
{
	detectInput();
	changeMouseTimeUpOrDown(0);
	changeMouseTimeUpOrDown(1);
	changeMouseTimeUpOrDown(2);
	setMousePosition();
}
void InputManager::copyOldStates()
{
	memcpy(oldKeyState,keyState,256);
	oldMouseState = mouseState;
}
float InputManager::distanceVector(D3DXVECTOR2 vector1,D3DXVECTOR2 vector2)
{
	float distance=((vector2.x-vector1.x)*(vector2.x-vector1.x))+((vector2.y-vector1.y)*(vector2.y-vector1.y));
	return distance;
}
D3DXVECTOR2 InputManager::getDeltaMouse()
{
	D3DXVECTOR2 returnMouseVal;
	returnMouseVal.x = mouseState.lX/1.0f;
	returnMouseVal.y = mouseState.lY/1.0f;
	return returnMouseVal;
}